home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Aminet 30
/
Aminet 30 (1999)(Schatztruhe)[!][Apr 1999].iso
/
Aminet
/
util
/
libs
/
chunky_dev.lha
/
chunky_dev
/
Source
/
chunkyp2c.asm
< prev
next >
Wrap
Assembly Source File
|
1998-12-28
|
8KB
|
387 lines
;------------------------------------------------------------------------------
;
; 100% systemfriendly PlanarToChunky converter for use with intuition
; screens in applications/games/whatever.
;
; Coded in 1994 by Morten Eriksen.
; Reach me through email: mortene@stud.unit.no.
;
; Use and modify as you like - give credit where appropriate.
;
; Timings on my A1200 with 68EC020 and 32-bit fastram:
;
; Testcase Dimensions This routine C='s ReadPixelArray8
;
; 1 320x256x5 - 10 frames (0.20 seconds) 41 frames
; 2 320x256x8 - 16 frames (0.32 seconds) 51 frames
; 3 640x512x4 - 34 frames (0.68 seconds) 158 frames
; 4 1024x1024x1 - 35 frames (0.70 seconds) 312 frames
; 5 752x578x8 - 89 frames (1.78 seconds) 312 frames
;
; Please suggest speed-ups in the code if you see any (by changing the
; algorithm, using other instructions with less executiontime, better
; pipelining, etc etc). The 'convert32pixels' is of course the bottleneck,
; as this subroutine accounts for almost all processing done in the
; converter.
;
; Some modifications (stack use instead global data, no 68000 support) in
; 1998 by Stephan Rupprecht
;
;------------------------------------------------------------------------------
xdef PlanarToChunkyAsm
;------------------------------------------------------------------------------
; This routine takes a buffer of chunkybytes and fills it with converted
; planar datas from the source BitMap.
;
; As a replacement for C='s ReadPixelArray8 routine, this one is more than
; three times as fast (in worst case) and works directly on bitmaps (instead
; of RastPorts). All cases handled (any width and height > 0, no alignment
; restrictions). Works on OCS/ECS/AGA, all Kickstarts and any MC680x0 CPU.
; The downside is that it does not do clipping and does not work with
; interleaved bitmaps (support for interleaved bitmaps should be piece of
; cake to implement, though).
;------------------------------------------------------------------------------
;
; C interface:
;
; extern void __asm PlanarToChunkyAsm(register __a0 struct p2cStruct *);
;
; struct p2cStruct
; {
; struct BitMap *bmap;
; UWORD startX, startY, width, height;
; UBYTE *chunkybuffer;
; } p2c;
;
; p2c.bmap = mybitmap;
; p2c.startX = x0;
; p2c.startY = y0;
; p2c.width = x1 - x0 + 1;
; p2c.height = y1 - y0 + 1;
; p2c.chunkybuffer = chunkybytes;
;
; SyncSBitMap(mywindow->RPort->Layer);
; PlanarToChunkyAsm(&p2c);
;------------------------------------------------------------------------------
;
; Assembler interface:
;
; In: a0 - p2c struct.
; Out: Nothing.
;------------------------------------------------------------------------------
; ** BitMap struct **
BytesPerRow EQU 0 ; UWORD
Rows EQU 2 ; UWORD
Flags EQU 4 ; UBYTE
Depth EQU 5 ; UBYTE
Pad EQU 6 ; UWORD
Planes EQU 8 ; PLANEPTRs [8]
; ** p2c struct **
bmap EQU 0 ; struct BitMap *
startX EQU 4 ; UWORD
startY EQU 6 ; UWORD
width EQU 8 ; UWORD
height EQU 10 ; UWORD
chunkybuffer EQU 12 ; UBYTE *
; **
buffer EQU 0
lastplaneptr EQU 32
Width EQU 36
Height EQU 38
Modulo EQU 40
leftpix EQU 42
rightpix EQU 44
insidebyte EQU 46
depth EQU 48
sizeof_buffer EQU 52
;------------------------------------------------------------------------------
Section code,CODE
PlanarToChunkyAsm:
movem.l d2-d7/a2-a6,-(sp)
lea.l -sizeof_buffer(sp),sp
lea.l madetable(pc),a2
tst.b (a2) * need only make bitspreadtable on first call
bne.s table_made
* makes the bitspread table *
* Do not destroy a0! *
make_table:
lea p2c,a1
moveq #0,d0
more_table
move.b d0,d1
moveq #8-1,d2
byteloop
btst #7,d1
beq.s zero
move.b #1,(a1)+
bra.s one
zero clr.b (a1)+
one add.b d1,d1
dbra d2,byteloop
addq #1,d0
cmp.w #256,d0
beq.s table_done
bra.s more_table
table_done
move.b #1,(a2)
table_made
move.l bmap(a0),a1
move.l chunkybuffer(a0),a3
lea p2c,a4
moveq #0,d1
move.w startX(a0),d0
andi.w #%111,d0
tst.w d0
beq.s noleftpix
moveq #8,d1
sub.w d0,d1
noleftpix
move.w d1,leftpix(sp)
move.w width(a0),d0
move.w d0,Width(sp)
hit cmp.w d1,d0
bhs.s notinsidebyte
move.b #1,insidebyte(sp)
moveq #0,d1
bra.s isinside
notinsidebyte
clr.b insidebyte(sp)
move.w Width(sp),d0
sub.w leftpix(sp),d0
move.w d0,d1
lsr.w #5,d0
lsl.w #5,d0
sub.w d0,d1
isinside
move.w d1,rightpix(sp)
* find initial offset in bytes into bitmap given by (startX, startY)
moveq #0,d0
move.w startX(a0),d0
lsr.w #3,d0
move.w startY(a0),d1
tst.w d1
beq.s line0
moveq #0,d2
move.w BytesPerRow(a1),d2
subq #1,d1
makeoffset
add.l d2,d0
dbra d1,makeoffset
line0 move.l d0,a2
tst.w leftpix(sp)
beq.s nol1
subq #3,a2
nol1 move.w Width(sp),d0
sub.w rightpix(sp),d0
move.w BytesPerRow(a1),d1
lsr.w #3,d0
sub.w d0,d1
move.w d1,Modulo(sp)
tst.b insidebyte(sp)
bne.s nol2
tst.w leftpix(sp)
beq.s nol2
subq #4,Modulo(sp)
nol2
move.w height(a0),Height(sp)
; a0 - c2p struct, a1 - bmap,
; a2 - offset from Planes pointer, a3 - chunkybuffer
; a4 - bitspread table
move.l a1,a6
add.w #Planes,a6
moveq #0,d0
move.b Depth(a1),d0
move.w d0,depth(sp)
lsl.w #2,d0
add.l d0,a6
move.l a6,lastplaneptr(sp)
convertline
tst.b insidebyte(sp)
beq.s notinsidesinglebyte
bsr.w convert32pixels
lea buffer+32(sp),a5
movem.l d0-d7,-(a5)
moveq #32,d0
sub.w leftpix(sp),d0
add.l d0,a5
move.w Width(sp),d0
subq #1,d0
singleinsert
move.b (a5)+,(a3)+
dbra d0,singleinsert
bra.w linedone
notinsidesinglebyte
tst.w leftpix(sp)
beq.s noleftpixels
tst.w Width(sp)
beq.w linedone
bsr.w convert32pixels
lea buffer+32(sp),a5
movem.l d0-d7,-(a5)
moveq #32,d0
sub.w leftpix(sp),d0
add.l d0,a5
move.w leftpix(sp),d0
move.w d0,d1
subq #1,d0
leftinsert
move.b (a5)+,(a3)+
dbra d0,leftinsert
sub.w d1,Width(sp)
addq #4,a2
noleftpixels
cmp.w #32,Width(sp)
blo.s trailbits
bsr.w convert32pixels
flushall
add.w #32,a3
movem.l d0-d7,-(a3)
add.w #32,a3
nolongflush
sub.w #32,Width(sp)
addq #4,a2
bra.b noleftpixels
trailbits
tst.w Width(sp)
beq.s linedone
bsr.b convert32pixels
lea buffer+32(sp),a5
movem.l d0-d7,-(a5)
move.w rightpix(sp),d0
subq #1,d0
rightinsert
move.b (a5)+,(a3)+
dbra d0,rightinsert
linedone
move.w width(a0),Width(sp)
add.w Modulo(sp),a2
subq #1,Height(sp)
tst.w Height(sp)
bne.w convertline
lea.l sizeof_buffer(sp),sp
movem.l (sp)+,d2-d7/a2-a6
rts
madetable dc.w 0
;------------------------------------------------------------------------------
cnop 0,8
convert32pixels:
move.l a3,-(sp)
move.l a0,-(sp)
move.w depth+12(sp),a3
move.l lastplaneptr+12(sp),a6
move.l -(a6),a5
add.l a2,a5
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
movem.l 0(a4,d7.w),d0/d1
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
movem.l 0(a4,d7.w),d2/d3
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
movem.l 0(a4,d7.w),d4/d5
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
movem.l 0(a4,d7.w),d6/d7
convert32pixelsloop
subq.w #1,a3
cmp.w #0,a3
beq.s done
move.l -(a6),a5
add.l a2,a5
move.w d7,a0
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
add.l d0,d0
or.l 0(a4,d7.w),d0
add.l d1,d1
or.l 4(a4,d7.w),d1
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
add.l d2,d2
or.l 0(a4,d7.w),d2
add.l d3,d3
or.l 4(a4,d7.w),d3
clr.w d7
move.b (a5)+,d7
lsl.w #3,d7
add.l d4,d4
or.l 0(a4,d7.w),d4
add.l d5,d5
or.l 4(a4,d7.w),d5
move.w a0,d7
move.w d5,a0
clr.w d5
move.b (a5)+,d5
lsl.w #3,d5
add.l d6,d6
or.l 0(a4,d5.w),d6
add.l d7,d7
or.l 4(a4,d5.w),d7
move.w a0,d5
bra.s convert32pixelsloop
done move.l (sp)+,a0
move.l (sp)+,a3
rts
;------------------------------------------------------------------------------
Section tables,BSS
cnop 0,8
* bitspread table *
p2c ds.b 256*8
;------------------------------------------------------------------------------
END